﻿using System.Linq.Expressions;

namespace Aore.Core.Repository.Dapper.Db.Contrib;

public class DbBuilder<T> where T : class
{
  private readonly DbCondition _condition = new DbCondition();

  public DbBuilder<T> Where(Expression<Func<T, bool>> predicate)
  {
    var condition = ParseExpression(predicate);
    _condition.And(condition);
    return this;
  }

  public DbBuilder<T> And(Expression<Func<T, bool>> predicate)
  {
    var condition = ParseExpression(predicate);
    _condition.And(condition);
    return this;
  }

  public DbBuilder<T> Or(Expression<Func<T, bool>> predicate)
  {
    var condition = ParseExpression(predicate);
    _condition.Or(condition);
    return this;
  }

  public DbBuilder<T> OrderBy<TKey>(Expression<Func<T, TKey>> keySelector)
  {
    var member = GetMemberName(keySelector.Body);
    _condition.OrderByAsc(member);
    return this;
  }

  public DbBuilder<T> OrderByDescending<TKey>(Expression<Func<T, TKey>> keySelector)
  {
    var member = GetMemberName(keySelector.Body);
    _condition.OrderByDesc(member);
    return this;
  }

  public DbBuilder<T> Page(int page, int pageSize)
  {
    _condition.Page(page, pageSize);
    return this;
  }

  public DbCondition Build()
  {
    return _condition;
  }

  private string ParseExpression(Expression expression)
  {
    // 简化的表达式解析，实际项目中需要更复杂的解析逻辑
    return expression.ToString();
  }

  private string GetMemberName(Expression expression)
  {
    if (expression is MemberExpression member)
      return member.Member.Name;
        
    if (expression is UnaryExpression unary && unary.Operand is MemberExpression unaryMember)
      return unaryMember.Member.Name;
            
    throw new ArgumentException("Invalid expression");
  }
}